part of '../../flutter_ns_ble.dart';

extension F1EcgData on Peripheral {
  Stream<EcgData<List<List<double>>>> get f1EcgData => notifyEvent
      .where((e) => e.cmd == CMD.ecgData)
      .map((e) => e.data)
      .whereNotNull()
      .map((value) {
        final byteData = value;
        final order = byteData.first;

        /// 4 通道
        final channel = 4;
        final byteCount = 3;
        List<List<double>> ecgData = List.generate(channel, (i) => []);
        final data = value.sublist(1).chunked(channel * byteCount).toList();

        for (var lineData in data) {
          final line = lineData.chunked(byteCount).toList();
          // lineData.chunked(3).forEach((data) => print("${calcF1EcgData4Channel(data.toList())}"));
          for (int channelIndex = 0; channelIndex < channel; channelIndex++) {
            final byteArray = line[channelIndex];
            final value = _calcF1EcgData4Channel(byteArray);
            ecgData[channelIndex].add(value);
          }
        }
        // print("$ecgData");
        return EcgData(order: order, data: ecgData);
      });
}

// import 'dart:math';
// import 'dart:typed_data';

// import 'package:ble_plugin/src/ble_ext.dart';

/// 将输出的心电数据转换回输入电压的最直接的方法是将数据与0x800000进行逻辑“与”计算并MSB（最高有效位）。
/// MSB等于0，即为正数，将十进制等效值乘以LSB值为电压值。
/// 如果MSB=1，即为负数数，则必须首先从十进制等效值中减去2^n，然后乘以LSB值。
///例如：VREF=4.5 V，N=24bit，增益=24，我们可以计算LSB。
///LSB = (2 x VREF)/ Gain / (2^n - 1)= (2 x 4.5)/ 24 / (2^24 - 1) = 22.352nV（纳伏）；
///输出心电数据0x147AE1，最高位为0是正数，对应于+30mV的输入电压。
///输出心电数据0xD70A3D，最高位为1是负数，对应于-60mV的输入电压。
///12导联的增益为12；
double _calcF1EcgData4Channel(
  List<int> byteArray, {
  double VREF = 4.5,
  int Gain = 24,
  int bitCount = 24,
}) {
  var num = Uint8List.fromList([
    0,
    ...byteArray,
  ]).buffer.asByteData().getInt32(0, Endian.big);

  final LSB = 2 * VREF / Gain / (pow(2, bitCount) - 1);
  final MSB = (num & 0x800000) >> (bitCount - 1);
  // print("MSB:${MSB}");
  final value = MSB == 0 ? num * LSB : (num - pow(2, bitCount)) * LSB;
  return value * 1000;
}

List<int> reverseCalcF1EcgData4Channel(
  double value, {
  double VREF = 4.5,
  int Gain = 24,
  int bitCount = 24,
}) {
  var num = value / 1000;

  // 计算LSB
  final LSB = 2 * VREF / Gain / (pow(2, bitCount) - 1);

  num = num > 0 ? num / LSB : (num + pow(2, bitCount)) / LSB;
  // print("num:${num}");
  // print("LSB:${LSB}");
  // print("num:${num / LSB}");

  var byteData = ByteData(4);
  byteData.setInt32(0, num.toInt(), Endian.little);
  // 将反转后的整数转换为字节数组

  return byteData.buffer.asUint8List(0, 3);
}
